
package com.shiku.utils;


import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.util.Random;
import javax.imageio.ImageIO;


public class ValidateCode {
    private int width = 160;

    private int height = 40;

    private int codeCount = 5;

    private int lineCount = 100;

    private String code = null;

    private BufferedImage buffImg = null;

    private char[] codeSequence = new char[]{'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'J', 'K', 'L', 'N', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'X', 'Y', '2', '3', '4', '5', '6', '7', '8', '9'};


    public ValidateCode() {

        createCode();

    }


    public ValidateCode(int width, int height) {

        this.width = width;

        this.height = height;

        createCode();

    }


    public ValidateCode(int width, int height, int codeCount, int lineCount) {

        this.width = width;

        this.height = height;

        this.codeCount = codeCount;

        this.lineCount = lineCount;

        createCode();

    }


    public void createCode() {

        int x = 0, fontHeight = 0, codeY = 0;

        int red = 0, green = 0, blue = 0;


        x = this.width / this.codeCount;

        fontHeight = this.height - 4;

        codeY = this.height - 8;


        this.buffImg = new BufferedImage(this.width, this.height, 1);

        Graphics2D g = this.buffImg.createGraphics();


        Random random = new Random();


        g.setColor(Color.WHITE);

        g.fillRect(0, 0, this.width, this.height);


        ImgFontByte imgFont = new ImgFontByte();

        Font font = imgFont.getFont(fontHeight);

        g.setFont(font);


        for (int i = 0; i < this.lineCount; i++) {

            int xs = random.nextInt(this.width);

            int ys = random.nextInt(this.height);

            int xe = xs + random.nextInt(this.width / 8);

            int ye = ys + random.nextInt(this.height / 8);

            red = random.nextInt(255);

            green = random.nextInt(255);

            blue = random.nextInt(255);

            g.setColor(new Color(red, green, blue));

            g.drawLine(xs, ys, xe, ye);

        }


        StringBuffer randomCode = new StringBuffer();


        for (int j = 0; j < this.codeCount; j++) {

            String strRand = String.valueOf(this.codeSequence[random.nextInt(this.codeSequence.length)]);


            red = 0;

            green = 0;

            blue = 0;

            g.setColor(new Color(red, green, blue));

            g.drawString(strRand, j * x, codeY);


            randomCode.append(strRand);

        }


        this.code = randomCode.toString();

    }


    public void write(String path) throws IOException {

        File file = new File(path);


        OutputStream sos = new FileOutputStream(path);

        write(sos);

    }


    public void write(OutputStream sos) throws IOException {

        ImageIO.write(this.buffImg, "png", sos);

        sos.close();

    }


    public BufferedImage getBuffImg() {

        return this.buffImg;

    }


    public String getCode() {

        return this.code;

    }


    public class ImgFontByte {

        public Font getFont(int fontHeight) {

            try {

                Font baseFont = Font.createFont(0, new ByteArrayInputStream(hex2byte(getFontByteStr())));

                return baseFont.deriveFont(0, fontHeight);

            } catch (Exception e) {

                return new Font("Arial", 0, fontHeight);

            }

        }


        private byte[] hex2byte(String str) {

            if (str == null) {
                return null;
            }

            str = str.trim();

            int len = str.length();

            if (len == 0 || len % 2 == 1) {

                return null;

            }

            byte[] b = new byte[len / 2];

            try {

                for (int i = 0; i < str.length(); i += 2) {

                    b[i / 2] =
                            (byte) Integer.decode("0x" + str.substring(i, i + 2)).intValue();

                }

                return b;

            } catch (Exception e) {

                return null;

            }

        }


        private String getFontByteStr() {

            return null;

        }

    }

}


